﻿using RM.Infrastructure.DomainBase;
using RM.Insfrastructure.ResponsitoryFramework;
using System;
using System.Collections.Generic;
using System.Data;
using System.Data.Common;
using System.Data.SqlClient;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace RM.Insfrastructure.Respositories
{
    public abstract class SqlServerRepositoryBase<T> : RepositoryBase<T>
        where T : EntityBase
    {
        #region Private Fields

        private const string DATA_SOURCE = "QUOCVU-PC";
        private const string DATABASE_NAME = "tour_management";
        private string connectionString;
        private SqlCommand command;
        private SqlConnection connection;


        // private Data database;
        private string baseQuery;// define their own base query cho their Aggregate
        private string baseWhereClause;
        private string entityName;// delete


        #endregion

        #region constructutor
        protected SqlServerRepositoryBase()
        {
            connectionString = "Data Source=" + DATA_SOURCE + ";Initial Catalog=" + DATABASE_NAME + ";Integrated Security=True;Connect Timeout=15;Encrypt=False;TrustServerCertificate=False";
            connection = new SqlConnection(connectionString);
        }

        #endregion

        #region Properties

        internal string BaseQuery
        {
            get { return this.baseQuery; }
        }

        protected string EntityName
        {
            get { return this.entityName; }
        }


        #endregion



        #region abstract methods
        protected abstract string GetBaseQuery();
        protected abstract string GetBaseWhereClause();
        protected abstract string GetEntityName();


        #endregion

        #region Internal Methods

        //internal List<T> BuildEntitiesFromSql(StringBuilder builder)
        //{
        //    return this.BuildEntitiesFromSql(builder.ToString());
        //}

        #endregion

        #region Protected Methods

        protected SqlDataReader ExecuteReader(string sql)
        {
            try
            {
                connection.Open();
                command = new SqlCommand(sql);
                return command.ExecuteReader();
            }
            catch (Exception ex)
            {
                Console.WriteLine("error when execute sql: " + ex.ToString());
            }
            finally 
            {
                connection.Close();
            }
            return null;
        }

        //protected virtual T BuildEntityFromSql(string sql)
        //{
        //    T entity = default(T);
        //    using (IDataReader reader = this.ExecuteReader(sql))
        //    {
        //        if (reader.Read())
        //        {
        //            entity = this.BuildEntityFromReader(reader);
        //        }
        //    }
        //    return entity;
        //}

        //protected virtual T BuildEntityFromReader(SqlDataReader reader)
        //{
        //    //T entity = this.entityFactory.BuildEntity(reader);
        //    //if (this.childCallbacks != null && this.childCallbacks.Count > 0)
        //    //{
        //    //    object childKeyValue = null;
        //    //    DataTable columnData = reader.GetSchemaTable();
        //    //    foreach (string childKeyName in this.childCallbacks.Keys)
        //    //    {
        //    //        if (DataHelper.ReaderContainsColumnName(columnData, childKeyName))
        //    //        {
        //    //            childKeyValue = reader[childKeyName];
        //    //        }
        //    //        else
        //    //        {
        //    //            childKeyValue = null;
        //    //        }
        //    //        this.childCallbacks[childKeyName](entity, childKeyValue);
        //    //    }
        //    //}
        //    //return entity;
        //    return null;
        //}

        //protected virtual List<T> BuildEntitiesFromSql(string sql)
        //{
        //    List<T> entities = new List<T>();
        //    using (SqlDataReader reader = this.ExecuteReader(sql))
        //    {
        //        while (reader.Read())
        //        {
        //            entities.Add(this.BuildEntityFromReader(reader));
        //        }
        //    }
        //    return entities;
        //}

        //protected virtual string BuildBaseWhereClause(object key)
        //{
        //    return string.Format(this.baseWhereClause, key);
        //}

        //protected virtual StringBuilder GetBaseQueryBuilder()
        //{
        //    StringBuilder builder = new StringBuilder(50);
        //    builder.Append(this.baseQuery);
        //    return builder;
        //}

     
        #endregion
    }
}
